/**
 * Place holder for copyright, needs to be replaced before release.
 */
package com.softao.ming.gde.internal.ui.wizard.export;

import java.util.Set;
import java.util.TreeSet;

import org.eclipse.core.runtime.IConfigurationElement;
import org.eclipse.core.runtime.IExtension;
import org.eclipse.jface.dialogs.Dialog;
import org.eclipse.jface.wizard.WizardPage;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Combo;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Group;

import com.softao.ming.gde.internal.core.export.GdeApplicationExportInfo;
import com.softao.ming.gde.internal.core.pde.PdeCoreUtil;
import com.softao.ming.gde.internal.ui.block.LocationTextBlock;

/**
 * 
 */
public class ExportGdeApplicationStep0Page extends WizardPage {
	class Listener extends SelectionAdapter implements ModifyListener {
		public void widgetSelected(SelectionEvent e) {
			doSelect(e);
		}
		
		@Override
		public void widgetDefaultSelected(SelectionEvent e) {
			doSelect(e);
		}
		
		private void doSelect(SelectionEvent e) {
			Object source = e.getSource();
			if (source == mProductButton) {
				boolean enabled = mProductButton.getSelection();
				mProductCombo.setEnabled(enabled);
				mApplicationCombo.setEnabled(!enabled);
			}
			buildExportInfo();
		}

		@Override
		public void modifyText(ModifyEvent e) {
			buildExportInfo();
		}
	}

	private GdeApplicationExportInfo mExportInfo;
	private Combo mApplicationCombo;
	private Button mProductButton;
	private Combo mProductCombo;
	private Button mApplicationButton;
	private LocationTextBlock mConfigurationLocationText;
	private LocationTextBlock mOutputLocationText;
	private Listener mListener = new Listener();
	
	/**
	 * @param pageName
	 */
	protected ExportGdeApplicationStep0Page(String pageName) {
		super(pageName);
		setTitle("Export GDE Application");
	}

	@Override
	public void createControl(Composite parent) {
		initializeDialogUnits(parent);

		Composite container = new Composite(parent, SWT.NULL);
		GridData layoutData = new GridData(GridData.FILL_BOTH);
		GridLayout layout = new GridLayout(1, true);
		container.setLayout(layout);
		container.setLayoutData(layoutData);
		
		Group composite = new Group(container, SWT.SHADOW_IN);
		composite.setText("Target");
		layout = new GridLayout(2, false);
		composite.setLayout(layout);
		layoutData = new GridData(GridData.FILL_HORIZONTAL);
		composite.setLayoutData(layoutData);
		
		createProductSection(composite);
		createApplicationSection(composite);
		
		composite = new Group(container, SWT.SHADOW_IN);
		composite.setText("Configuration");
		layout = new GridLayout(2, false);
		composite.setLayout(layout);
		layoutData = new GridData(GridData.FILL_HORIZONTAL);
		composite.setLayoutData(layoutData);
		
		mConfigurationLocationText = new LocationTextBlock();
		mConfigurationLocationText.createControl(composite);
		mConfigurationLocationText.addModifyListener(mListener);

		composite = new Group(container, SWT.SHADOW_IN);
		composite.setText("Output:");
		layout = new GridLayout(2, false);
		composite.setLayout(layout);
		layoutData = new GridData(GridData.FILL_HORIZONTAL);
		composite.setLayoutData(layoutData);
		
		mOutputLocationText = new LocationTextBlock();
		mOutputLocationText.createControl(composite);
		mOutputLocationText.addModifyListener(mListener);
		

		setErrorMessage(null);
		setMessage("Export GWT Module.");
		setControl(container);
		Dialog.applyDialogFont(container);
		
		boolean useProduct = mProductButton.isEnabled();
		mProductButton.setSelection(useProduct);
		mProductCombo.setEnabled(useProduct);
		boolean useApplication = !useProduct && mApplicationButton.isEnabled();
		mApplicationButton.setSelection(useApplication);
		mApplicationCombo.setEnabled(useApplication);
		
		buildExportInfo();
		setPageComplete(isPageComplete());
	}

	private void createProductSection(Composite parent) {
		mProductButton = new Button(parent, SWT.RADIO);
		mProductButton.setText("Run a &product:");
		mProductButton.addSelectionListener(mListener);

		mProductCombo = new Combo(parent, SWT.READ_ONLY | SWT.DROP_DOWN);
		mProductCombo.setItems(getProductNames());
		mProductCombo.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
		mProductCombo.addSelectionListener(mListener);
		
		if (mProductCombo.getItemCount() == 0) {
			mProductButton.setEnabled(false);
		} else {
			mProductCombo.select(0);
		}
	}
	
	private void createApplicationSection(Composite parent) {
		mApplicationButton = new Button(parent, SWT.RADIO);
		mApplicationButton.setText("Run an &application:");

		mApplicationCombo = new Combo(parent, SWT.READ_ONLY | SWT.DROP_DOWN);
		mApplicationCombo.setItems(getApplicationNames());
		mApplicationCombo.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
		mApplicationCombo.addSelectionListener(mListener);
		
		if (mApplicationCombo.getItemCount() == 0) {
			mApplicationButton.setEnabled(false);
		} else {
			mApplicationCombo.select(0);
		}
	}
	
	private static TreeSet<String> getProductNameSet() {
		TreeSet<String> result = new TreeSet<String>();
		IExtension[] extensions = PdeCoreUtil.findExtensions("com.softao.ming.gwt.core.runtime.products", true); //$NON-NLS-1$
		for (int i = 0; i < extensions.length; i++) {
			IConfigurationElement[] elements = extensions[i].getConfigurationElements();
			for (IConfigurationElement element : elements) {
				if ("product".equals(element.getName())) {
					String id = element.getAttribute("id");
					if (id != null && id.trim().length() > 0) {
						result.add(id);
					}
				}
			}
		}
		return result;
	}

	private static String[] getProductNames() {
		TreeSet<String> result = getProductNameSet();
		return result.toArray(new String[result.size()]);
	}

	private static Set<String> getApplicationNameSet() {
		TreeSet<String> result = new TreeSet<String>();
		IExtension[] extensions = PdeCoreUtil.findExtensions("com.softao.ming.gwt.core.runtime.applications", true); //$NON-NLS-1$
		for (int i = 0; i < extensions.length; i++) {
			IConfigurationElement[] elements = extensions[i].getConfigurationElements();
			for (IConfigurationElement element : elements) {
				if ("application".equals(element.getName())) {
					String id = element.getAttribute("id");
					if (id != null && id.trim().length() > 0) {
						result.add(id);
					}
				}
			}
		}
		return result;
	}

	private static String[] getApplicationNames() {
		Set<String> result = getApplicationNameSet();
		return result.toArray(new String[result.size()]);
	}
	
	@Override
	public boolean isPageComplete() {
		if (mApplicationButton.getSelection()) {
			return mApplicationCombo.getSelectionIndex() >= 0;
		} else if (mProductButton.getSelection()) {
			return mProductCombo.getSelectionIndex() >= 0;
		} else {
			return false;
		}
	}
	
	private void buildExportInfo() {
		mExportInfo = new GdeApplicationExportInfo();
		mExportInfo.setConfigurationLocation(mConfigurationLocationText.getLocation());
		mExportInfo.setOutputLocation(mOutputLocationText.getLocation());
		if (mProductButton.getSelection()) {
			mExportInfo.setUseProduct(true);
			mExportInfo.setProductId(mProductCombo.getItem(mProductCombo.getSelectionIndex()));
		} else if (mApplicationButton.getSelection()) {
			mExportInfo.setUseProduct(false);
			mExportInfo.setApplicationId(mApplicationCombo.getItem(mApplicationCombo.getSelectionIndex()));
		} else {
			mExportInfo = null;
		}
	}
	
	/**
	 * @return the export information in the wizard.
	 */
	public GdeApplicationExportInfo getExportInfo() {
		return mExportInfo;
	}
}
